<template>
  <div class="api-doc-container">
    <el-card shadow="never">
      <template #header>
        <div class="card-header">
          <span>API 文档管理</span>
          <div>
            <el-button type="primary" :icon="Plus" @click="handleAdd">新增文档</el-button>
            <el-button type="success" :icon="Upload" @click="importDialogVisible = true">导入文档</el-button>
          </div>
        </div>
      </template>

      <el-tabs v-model="activeTab" class="api-doc-tabs">
        <el-tab-pane label="API文档列表" name="list">
          <el-form :inline="true" :model="queryForm" class="query-form">
            <el-form-item label="文档标题">
              <el-input v-model="queryForm.title" placeholder="请输入文档标题" clearable />
            </el-form-item>
            <el-form-item label="文档状态">
              <el-select v-model="queryForm.status" placeholder="请选择状态" clearable>
                <el-option label="草稿" :value="0" />
                <el-option label="已发布" :value="1" />
                <el-option label="已下线" :value="2" />
              </el-select>
            </el-form-item>
            <el-form-item>
              <el-button type="primary" :icon="Search" @click="handleQuery">搜索</el-button>
              <el-button :icon="Refresh" @click="resetQuery">重置</el-button>
            </el-form-item>
          </el-form>

          <el-table :data="apiDocList" border highlight-current-row v-loading="loading">
            <el-table-column prop="docId" label="ID" width="80" align="center" />
            <el-table-column prop="title" label="文档标题" min-width="150" show-overflow-tooltip />
            <el-table-column prop="type" label="类型" width="100" align="center" />
            <el-table-column prop="description" label="描述" min-width="200" show-overflow-tooltip />
            <el-table-column label="状态" width="100" align="center">
              <template #default="scope">
                <el-tag :type="scope.row.status === 1 ? 'success' : (scope.row.status === 2 ? 'danger' : 'info')">
                  {{ formatStatus(scope.row.status) }}
                </el-tag>
              </template>
            </el-table-column>
            <el-table-column prop="createTime" label="创建时间" width="180" align="center" />
            <el-table-column prop="updateTime" label="更新时间" width="180" align="center" />
            <el-table-column label="操作" width="280" align="center" fixed="right">
              <template #default="scope">
                <el-button link type="primary" size="small" @click="handleDetail(scope.row)">详情</el-button>
                <el-button link type="primary" size="small" @click="handleEdit(scope.row)">修改</el-button>
                <el-button link type="primary" size="small" @click="handleExport(scope.row)">导出</el-button>
                <el-button
                  link
                  :type="scope.row.status === 1 ? 'warning' : 'success'"
                  size="small"
                  @click="handleChangeStatus(scope.row)"
                >
                  {{ scope.row.status === 1 ? '下线' : '发布' }}
                </el-button>
                <el-button link type="danger" size="small" @click="handleDelete(scope.row)">删除</el-button>
              </template>
            </el-table-column>
          </el-table>

          <el-pagination
            v-model:current-page="queryForm.pageNum"
            v-model:page-size="queryForm.pageSize"
            :page-sizes="[10, 20, 50, 100]"
            layout="total, sizes, prev, pager, next, jumper"
            :total="total"
            @size-change="handleQuery"
            @current-change="handleQuery"
          />
        </el-tab-pane>

        <el-tab-pane label="Swagger API" name="detail">
          <div v-loading="loadingDetail" class="detail-content">
            <template v-if="selectedDoc.url">
              <iframe :src="selectedDoc.url" frameborder="0" class="api-doc-iframe"></iframe>
            </template>
            <template v-else-if="selectedDoc.content">
              <el-tabs v-model="activeContentTab" class="api-doc-tabs-content">
                <el-tab-pane label="原始内容" name="raw-content">
                  <pre class="code-block">{{ formatContent(selectedDoc.content, selectedDoc.type) }}</pre>
                </el-tab-pane>
                <el-tab-pane label="预览" name="preview-content" v-if="selectedDoc.type === 'Swagger' || selectedDoc.type === 'OpenAPI'">
                  <div ref="previewContainer" class="api-doc-preview"></div>
                </el-tab-pane>
              </el-tabs>
            </template>
            <template v-else>
              <el-empty description="请从左侧列表选择一个API文档查看详情，或暂无文档内容/URL" />
            </template>
          </div>
        </el-tab-pane>
      </el-tabs>
    </el-card>

    <!-- 新增/修改弹窗 -->
    <el-dialog
      v-model="dialogVisible"
      :title="dialogTitle"
      width="60%"
      :close-on-click-modal="false"
      @closed="resetForm"
    >
      <el-form
        ref="apiDocFormRef"
        :model="apiDocForm"
        :rules="rules"
        label-width="100px"
        v-loading="formLoading"
      >
        <el-form-item label="文档标题" prop="title">
          <el-input v-model="apiDocForm.title" placeholder="请输入文档标题" />
        </el-form-item>
        <el-form-item label="文档类型" prop="type">
          <el-select v-model="apiDocForm.type" placeholder="请选择文档类型">
            <el-option label="Swagger" value="Swagger" />
            <el-option label="OpenAPI" value="OpenAPI" />
          </el-select>
        </el-form-item>
        <el-form-item label="文档描述" prop="description">
          <el-input v-model="apiDocForm.description" type="textarea" :rows="3" placeholder="请输入文档描述" />
        </el-form-item>
        <el-form-item label="文档URL" prop="url" v-if="apiDocForm.type === 'Swagger' || apiDocForm.type === 'OpenAPI'">
          <el-input v-model="apiDocForm.url" placeholder="请输入文档URL" />
        </el-form-item>
        <el-form-item label="文档内容" prop="content" v-else>
          <el-input v-model="apiDocForm.content" type="textarea" :rows="10" placeholder="请输入文档内容" />
        </el-form-item>
        <el-form-item label="文档状态" prop="status">
          <el-radio-group v-model="apiDocForm.status">
            <el-radio :label="0">草稿</el-radio>
            <el-radio :label="1">已发布</el-radio>
            <el-radio :label="2">已下线</el-radio>
          </el-radio-group>
        </el-form-item>
      </el-form>
      <template #footer>
        <span class="dialog-footer">
          <el-button @click="dialogVisible = false">取消</el-button>
          <el-button type="primary" @click="handleSubmit">确定</el-button>
        </span>
      </template>
    </el-dialog>

    <!-- 导入弹窗 -->
    <el-dialog
      v-model="importDialogVisible"
      title="导入API文档"
      width="30%"
      :close-on-click-modal="false"
      @closed="resetImportForm"
    >
      <el-upload
        ref="uploadRef"
        class="upload-demo"
        drag
        :auto-upload="false"
        :on-change="handleFileChange"
        :on-exceed="handleExceed"
        :limit="1"
        :show-file-list="true"
        accept=".json,.yaml,.yml"
      >
        <el-icon class="el-icon--upload"><upload-filled /></el-icon>
        <div class="el-upload__text">
          将文件拖放到此处或 <em>点击上传</em>
        </div>
        <template #tip>
          <div class="el-upload__tip">
            支持 .json, .yaml, .yml 文件
          </div>
        </template>
      </el-upload>
      <template #footer>
        <span class="dialog-footer">
          <el-button @click="importDialogVisible = false">取消</el-button>
          <el-button type="primary" @click="handleImportSubmit">导入</el-button>
        </span>
      </template>
    </el-dialog>
  </div>
</template>

<script setup>
import { ref, reactive, onMounted, nextTick, watch } from 'vue';
import { ElMessage, ElMessageBox } from 'element-plus';
import { Search, Refresh, Plus, UploadFilled, Upload } from '@element-plus/icons-vue';
import {
  getApiDocList,
  getApiDocDetail,
  addApiDoc,
  updateApiDoc,
  deleteApiDoc,
  updateApiDocStatus,
  importApiDoc,
  exportApiDoc,
  getApiDocCategories
} from '@/api/tool/apiDoc'; // 引入apiDoc.js中的接口

// 引入swagger-ui-dist
import SwaggerUIBundle from 'swagger-ui-dist/swagger-ui-bundle.js';
import SwaggerUIStandalonePreset from 'swagger-ui-dist/swagger-ui-standalone-preset.js';

const loading = ref(true);
const loadingDetail = ref(false); // 用于详情页的加载状态
const formLoading = ref(false);
const apiDocList = ref([]);
const total = ref(0);
const queryForm = reactive({
  pageNum: 1,
  pageSize: 10,
  title: '',
  status: null,
});

const dialogVisible = ref(false);
const dialogTitle = ref('');
const apiDocFormRef = ref(null);
const apiDocForm = reactive({
  docId: null,
  title: '',
  description: '',
  type: 'Swagger', // 默认Swagger
  url: '',
  content: '',
  status: 0, // 默认草稿
});

const rules = reactive({
  title: [{ required: true, message: '请输入文档标题', trigger: 'blur' }],
  type: [{ required: true, message: '请选择文档类型', trigger: 'change' }],
});

const importDialogVisible = ref(false);
const uploadFile = ref(null);
const uploadRef = ref(null);

const activeTab = ref('list'); // 默认激活列表页
const activeContentTab = ref('raw-content'); // 详情页默认激活原始内容tab
const selectedDoc = reactive({ // 存储当前选中的API文档详情
  docId: null,
  title: '',
  description: '',
  type: '',
  url: '',
  content: '',
  status: null,
});
const previewContainer = ref(null); // 预览容器引用

const formatStatus = (status) => {
  switch (status) {
    case 0:
      return '草稿';
    case 1:
      return '已发布';
    case 2:
      return '已下线';
    default:
      return '未知';
  }
};

const handleQuery = async () => {
  loading.value = true;
  try {
    const res = await getApiDocList(queryForm);
    apiDocList.value = res.data.list;
    total.value = res.data.total;
  } catch (error) {
    ElMessage.error('获取API文档列表失败');
    console.error(error);
  } finally {
    loading.value = false;
  }
};

const resetQuery = () => {
  queryForm.title = '';
  queryForm.status = null;
  queryForm.pageNum = 1;
  handleQuery();
};

const handleAdd = () => {
  dialogTitle.value = '新增API文档';
  dialogVisible.value = true;
  nextTick(() => {
    apiDocForm.docId = null;
    apiDocForm.title = '';
    apiDocForm.description = '';
    apiDocForm.type = 'Swagger';
    apiDocForm.url = '';
    apiDocForm.content = '';
    apiDocForm.status = 0;
    apiDocFormRef.value?.resetFields();
  });
};

const handleEdit = (row) => {
  dialogTitle.value = '修改API文档';
  dialogVisible.value = true;
  nextTick(() => {
    Object.assign(apiDocForm, row);
    // if (apiDocForm.type === 'Swagger' || apiDocForm.type === 'OpenAPI') {
    //   // 对于通过URL加载的文档，可能没有content字段，需要处理
    // }
  });
};

const handleSubmit = () => {
  apiDocFormRef.value?.validate(async (valid) => {
    if (valid) {
      formLoading.value = true;
      try {
        if (apiDocForm.docId) {
          await updateApiDoc(apiDocForm);
          ElMessage.success('修改成功');
        } else {
          await addApiDoc(apiDocForm);
          ElMessage.success('新增成功');
        }
        dialogVisible.value = false;
        handleQuery();
      } catch (error) {
        ElMessage.error(apiDocForm.docId ? '修改失败' : '新增失败');
        console.error(error);
      } finally {
        formLoading.value = false;
      }
    }
  });
};

const resetForm = () => {
  apiDocFormRef.value?.resetFields();
  Object.assign(apiDocForm, {
    docId: null,
    title: '',
    description: '',
    type: 'Swagger',
    url: '',
    content: '',
    status: 0,
  });
  uploadFile.value = null;
  uploadRef.value?.clearFiles();
};

const handleDelete = (row) => {
  ElMessageBox.confirm(`确定删除文档 "${row.title}" 吗？`, '提示', {
    confirmButtonText: '确定',
    cancelButtonText: '取消',
    type: 'warning',
  })
    .then(async () => {
      await deleteApiDoc(row.docId);
      ElMessage.success('删除成功');
      handleQuery();
    })
    .catch(() => {
      ElMessage.info('已取消删除');
    });
};

const handleChangeStatus = async (row) => {
  const newStatus = row.status === 1 ? 2 : 1; // 1: 发布 -> 2: 下线; 0/2: 草稿/下线 -> 1: 发布
  const statusText = newStatus === 1 ? '发布' : '下线';
  ElMessageBox.confirm(`确定要${statusText}文档 "${row.title}" 吗？`, '提示', {
    confirmButtonText: '确定',
    cancelButtonText: '取消',
    type: 'warning',
  })
    .then(async () => {
      await updateApiDocStatus(row.docId, newStatus);
      ElMessage.success(`${statusText}成功`);
      handleQuery();
    })
    .catch(() => {
      ElMessage.info('已取消操作');
    });
};

const handleExport = async (row) => {
  try {
    const res = await exportApiDoc(row.docId);
    const blob = new Blob([res], { type: 'application/octet-stream' });
    const url = URL.createObjectURL(blob);
    const link = document.createElement('a');
    link.href = url;
    link.download = `${row.title}.${row.type === 'Swagger' ? 'json' : 'yaml'}`; // 根据类型设置下载文件名
    document.body.appendChild(link);
    link.click();
    document.body.removeChild(link);
    URL.revokeObjectURL(url);
    ElMessage.success('导出成功');
  } catch (error) {
    ElMessage.error('导出失败');
    console.error(error);
  }
};

const handleFileChange = (file) => {
  uploadFile.value = file.raw;
};

const handleExceed = () => {
  ElMessage.warning('只能上传一个文件，请先移除当前文件');
};

const handleImportSubmit = async () => {
  if (!uploadFile.value) {
    ElMessage.warning('请选择要上传的文件');
    return;
  }
  formLoading.value = true;
  try {
    const formData = new FormData();
    formData.append('file', uploadFile.value);
    await importApiDoc(formData);
    ElMessage.success('导入成功');
    importDialogVisible.value = false;
    handleQuery();
  } catch (error) {
    ElMessage.error('导入失败');
    console.error(error);
  } finally {
    formLoading.value = false;
  }
};

const resetImportForm = () => {
  uploadFile.value = null;
  uploadRef.value?.clearFiles();
};

// ======================= 详情页相关逻辑集成 =======================

const handleDetail = async (row) => {
  activeTab.value = 'detail'; // 切换到详情标签页
  selectedDoc.docId = row.docId;
  activeContentTab.value = 'raw-content'; // 默认显示原始内容
  await fetchApiDocDetail();
};

const fetchApiDocDetail = async () => {
  if (!selectedDoc.docId) return;
  loadingDetail.value = true;
  try {
    const res = await getApiDocDetail(selectedDoc.docId);
    Object.assign(selectedDoc, res.data);
    // 如果文档内容不为空，并且当前是预览tab，则尝试渲染预览
    if (selectedDoc.content && activeContentTab.value === 'preview-content') {
      nextTick(() => {
        renderPreview();
      });
    }
  } catch (error) {
    ElMessage.error('获取API文档详情失败');
    console.error(error);
  } finally {
    loadingDetail.value = false;
  }
};

const formatContent = (content, type) => {
  try {
    if (type === 'Swagger' || type === 'OpenAPI') {
      // 尝试格式化JSON或YAML
      return JSON.stringify(JSON.parse(content), null, 2);
    } else {
      return content;
    }
  } catch (e) {
    return content; // 格式化失败则返回原始内容
  }
};

const renderPreview = () => {
  if (activeContentTab.value === 'preview-content' && previewContainer.value && selectedDoc.content) {
    try {
      const spec = JSON.parse(selectedDoc.content); // 假设内容是JSON格式
      if (selectedDoc.type === 'Swagger' || selectedDoc.type === 'OpenAPI') {
        // 清空旧的Swagger UI实例
        previewContainer.value.innerHTML = '';
        SwaggerUIBundle({
          spec: spec,
          domNode: previewContainer.value,
          deepLinking: true,
          presets: [SwaggerUIBundle.presets.apis, SwaggerUIStandalonePreset],
          plugins: [SwaggerUIBundle.plugins.DownloadUrl],
          layout: "StandaloneLayout"
        });
      } else {
        previewContainer.value.innerHTML = '<p style="color: #999; text-align: center;">暂不支持该类型文档的预览</p>';
      }
    } catch (e) {
      console.error("Failed to parse or render API document content:", e);
      previewContainer.value.innerHTML = '<p style="color: red; text-align: center;">文档内容解析失败，请检查格式。</p>';
    }
  }
};

watch(activeTab, (newTab) => {
  if (newTab === 'detail' && selectedDoc.docId) { // 只有切换到详情页且已选中文档时才加载详情
    activeContentTab.value = 'raw-content'; // 每次切换到详情tab时，默认显示原始内容
    fetchApiDocDetail();
  }
});

watch(activeContentTab, (newContentTab) => {
  if (newContentTab === 'preview-content' && selectedDoc.content) {
    nextTick(() => {
      renderPreview();
    });
  }
});

onMounted(() => {
  handleQuery();
});
</script>

<style lang="scss" scoped>
.api-doc-container {
  padding: 20px;

  .card-header {
    display: flex;
    justify-content: space-between;
    align-items: center;
  }

  .api-doc-tabs {
    .el-tab-pane {
      padding: 20px 0; // 给tab-pane内容一些内边距
    }
  }

  .query-form {
    margin-bottom: 18px;
  }

  .el-pagination {
    margin-top: 18px;
    justify-content: flex-end;
  }

  .detail-content {
    min-height: 500px; /* 适当增加高度 */
    display: flex;
    flex-direction: column;

    .api-doc-iframe {
      width: 100%;
      flex-grow: 1;
      border: none;
      min-height: 500px; // 确保iframe有足够高度
    }

    .api-doc-tabs-content {
      flex-grow: 1;
      display: flex;
      flex-direction: column;
      height: 100%; // 确保tab内容区域占满

      :deep(.el-tabs__content) {
        flex-grow: 1;
        display: flex;
        flex-direction: column;
        height: calc(100% - var(--el-tabs-header-height)); // 减去tab头的高度

        .el-tab-pane {
          flex-grow: 1;
          display: flex;
          flex-direction: column;
          padding: 0; // 内部tab-pane不需要额外padding
        }
      }
    }

    .code-block {
      background-color: #f5f5f5;
      padding: 15px;
      border-radius: 4px;
      overflow: auto;
      white-space: pre-wrap; /* 保持换行 */
      word-break: break-all; /* 单词内部断行 */
      max-height: 600px; /* 限制高度并滚动 */
      flex-grow: 1;
    }

    .api-doc-preview {
      flex-grow: 1;
      border: 1px solid #eee;
      border-radius: 4px;
      overflow: hidden; /* 确保内容在容器内 */
      // 防止Swagger UI生成不必要的滚动条
      :deep(.swagger-ui) {
        .opblock-tag-section {
          padding-bottom: 0;
        }
        .opblock-tag {
          margin-bottom: 0;
        }
        .scheme-container {
          margin-bottom: 0;
        }
        .markdown {
          p {
            word-break: break-all;
          }
        }
      }
    }
  }
}
</style> 